#ifndef _H_SOCKET_
#define _H_SOCKET_
#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <iostream>
#ifdef _WIN32
#include<Winsock2.h>
#include<WS2tcpip.h>
#define socklen_t unsigned int
#pragma comment(lib,"ws2_32.lib")
#else
#include<string.h>
#include<unistd.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<netinet/in.h>
#include<arpa/inet.h>
#include <mutex>
#define SOCKET int
#endif // Win
using namespace std;
#define IPV4 0x0001
#define IPV6 0x0002

#define TCP 0x0010
#define UDP 0x0020
#define MAX_SIZE 4096

class HSocket
{
public:
    //标志Socket
	HSocket(int flag);
    //获取Socket
    int HGetSocket();
	//关闭Socket
	void Hclose();
	~HSocket();
	//bind  Socket
	int Hbind(const sockaddr_in6& add);
	int Hbind(const sockaddr_in add);
	//listen
	int Hlisten(int backlog = 5);
	//accept
	SOCKET Haccept();
	//connect
	int Hconnect(const sockaddr_in6& add);
	int Hconnect(const sockaddr_in& add);

public:
	int flag;
	SOCKET s;
	sockaddr_in6 add;
	sockaddr_in add4;
};


class Common {
public:
	Common(int flag);
	~Common();

	int recvData(string& data,SOCKET s);
	int recvData(string& data, SOCKET s, sockaddr_in& cliAdd);
	int recvData(string& data, SOCKET s, sockaddr_in6& cliAdd);

	int sendData(const string& data, SOCKET s);
	int sendData(const string& data, SOCKET s, const sockaddr_in& add);
	int sendData(const string& data, SOCKET s, const sockaddr_in6& add);
public:
    std::mutex rcvlock;//读取数据锁
    std::mutex sendlock;//发送数据锁
	int flag;
	HSocket* sock;
};

class HServerBase : public Common {
public:
	HServerBase(int flag);
	~HServerBase();
	int initServer(const u_short& port, int backlog = 5);
	virtual int startServer();
	virtual void stopServer();
public:
	int status;
};


class HClientBase :public Common {
public:
	HClientBase(int flag);
	~HClientBase();
	int initClient(const char* ip, u_short port);
	virtual int startClient();
public:
	sockaddr_in6 serverAdd;
	sockaddr_in serverAdd4;
};
#endif
